Introduction to R
and {circumplex}

SITAR 2022 | 2022-07-30
Jeffrey Girard | Univ. of Kansas

Overview

Instructor

Jeffrey Girard, PhD
www.jmgirard.com
jmgirard@ku.edu

Background

  • Assistant Professor, University of Kansas
  • Research Postdoc, Carnegie Mellon University
  • PhD Student, University of Pittsburgh

Research Areas

  • Psychological Assessment
  • Affective/Interpersonal Communication
  • Applied Statistics and Machine Learning
  • Data Science and Software Engineering

R Rationale

  1. Think of your computer as the engine of a car
    • It provides raw power for computation
  1. The R language is like the controls for the car
    • It lets you apply and direct that power
  1. RStudio is like a fancy dashboard for the car
    • It adds extra information and convenience
  1. An R package is like an add-on for the car
    • It adds new features and capabilities

Workshop Goals

  • This is a beginner-friendly workshop aimed at social scientists with little to no experience in R
  • My goal is to “grant your learner’s permit
    • How to navigate around RStudio
    • How to do calculations in R
    • How to import data into R
  • I will introduce you to the {circumplex} package
    • How to score and norm an instrument
    • How to use the Structural Summary Method
    • How to generate tables and figures

Introduction to R

Installing R

Windows

  1. Open a web browser
  2. Visit cloud.r-project.org
  3. Click “Download R for Windows”
  4. Click the “base” subdirectory link
  5. Click “Download R-4.X.X” (e.g., 4.2.1)
  6. Run the downloaded .exe file
  7. Select all the default options
  8. Complete the installation wizard

Mac OS

  1. Open a web browser
  2. Visit cloud.r-project.org
  3. Click “Download R for macOS”
  4. Click “R-4.X.X.pkg” (e.g., 4.2.1)
  5. Run the downloaded .pkg file
  6. Select all the default options
  7. Complete the installation wizard

Installing RStudio

Windows

  1. Open a web browser
  2. Visit rstudio.com/download
  3. Scroll down until you find the table
    under the “All Installers” section
  4. Find the row for “Windows 10/11”
  5. Click “RStudio-2022.XX.X-XXX.exe”
  6. Run the downloaded .exe file
  7. Select all the default options
  8. Complete the installation wizard

Mac OS

  1. Open a web browser
  2. Visit rstudio.com/download
  3. Scroll down until you find the table
    under the “All Installers” section
  4. Find the row for “macOS 10.15+”
  5. Click “RStudio-2022.XX.X-XXX.dmg”
  6. Run the downloaded .dmg file
  7. Drag the RStudio icon to your
    Applications folder (if you want)

RStudio Window

R will Grant your Wishes

  • R is like a well-meaning but overly literal genie

    • It has the power to grant almost any wish
    • But we must phrase our wishes carefully!
    • We will always get what we ask for…
    • …but not always what we wanted.
  • Mastering the R language means learning…

    • How to properly phrase commands
    • How to decipher error messages
    • How to view code from R’s perspective
    • How to detect and correct small mistakes

Console Live Coding

# Addition and Subtraction

10+3

10-3

10 + 3 # spaces are optional but recommended

10 - 3

# ==============================================================================

# Multiplication and Division

10 * 3 # correct

10 x 3 # error

10 / 3 # correct

10 \ 3 # error

Assignment

  • It is often useful to store data in named objects
    • This makes the data easier to use and re-use
    • This makes the code easier to write and read
  • Which command is easier to follow?
    1. Dial 7 8 5 8 6 4 0 8 4 1
    2. Call Office Phone
  • Named objects are created using assignment
    • Give a name then an arrow then the data

office <- 7858640841

Assignment Live Coding

# LESSON: Assigning and printing

x <- 2
x

# ==============================================================================

# USECASE: Using an object in math (a la algebra) 

x * 4

2 * 4

(x * x) - (10 + x)

# ==============================================================================

# LESSON: You must use assignment to update an object

x

x + 1
x # still 2

x <- x + 1
x # updated to 3

# ==============================================================================

# LESSON: R is case sensitive

q <- 10
q

Q <- 20
Q

q # still 10

Naming

  • Object names can only include:
    • Letters: a-Z
    • Numbers: 0-9
    • Underscores: _
    • Periods: .
  • Additional Rules:
    • Must start with a letter or period
    • Cannot contain spaces or dashes
    • Cannot contain other symbols
    • Names are case-sensitive (ageAge)

Naming Live Coding

# LESSON: Good names are a balancing act

x <- 93 # what is it?

rate <- 93 # too short

heart_rate_in_beats_per_minute <- 93 # too long

heart_rate <- 93 # just right

# ==============================================================================

# PITFALL: Don't try to include spaces or dashes in names

heart rate <- 93 # error

heart-rate <- 93 # error

# ==============================================================================

# PITFALL: Don't try to include special symbols

age@time2 <- 12 # error

age_time2 <- 12 # correct

# ==============================================================================

# PITFALL: Don't try to put a number or underscore first

heart_rate_1 <- 93 # correct

1_heart_rate <- 93 # error

_heart_rate <- 93 # error

Functions

  • Recipes allow chefs to cook up tasty treats
    • Recipes call for ingredients
    • Recipes involve one or more steps
    • Steps transform ingredients into treats
  • Functions are like customizable recipes
    • Functions call for inputs (“arguments”)
    • Functions involve one or more lines of code
    • Code transforms inputs into outputs
    • Using functions requires parentheses (usually)

out <- f(in1, in2)

Functions Live Coding

# USECASE: Function can perform a task more easily and readably

# TEMPLATE: output <- function_name(input)

9 ^ (1 / 2)

x <- sqrt(9)
x

# ==============================================================================

# LESSON: We can also use functions to transform objects

y <- 9

sqrt(y)

# ==============================================================================

# LESSON: We can even use functions to transform the result of calculations

2 / 3

round(2 / 3)

# ==============================================================================

# LESSON: We can customize what a function does using arguments

# TEMPLATE: output <- function_name(argument, argument_name = argument_value)

round(2 / 3, digits = 2)

round(2 / 3, digits = 3)

# ==============================================================================

# LESSON: Some arguments are optional because they have default values

round(2 / 3) # the default value for digits is 0

round(2 / 3, digits = 0)

Vectors

  • Vectors combine similar objects into a collection
    • I like to imagine a train pulling multiple cars
    • A vector is one object with many sub-objects
    • We refer to each sub-object as an element
  • Some functions transform each element in turn
    • Double the amount of cargo in every train car
  • Some functions summarize across elements
    • Calculate the total cargo across all train cars

v <- c(1, 2, 3)

Vectors Live Coding

# LESSON: We can combine multiple elements into a vector

# TEMPLATE: vector_name <- c(element1, element2, element3)

x <- 4 9 16 25 # error

x <- c(4, 9, 16, 25)
x

y <- c(2, 3)
y

# ==============================================================================

# LESSON: We can also combine multiple vectors and elements

z <- c(x, y)
z

# ==============================================================================

# USECASE: Math operators will transform each element individually

x + 1

x * 3

# ==============================================================================

# USECASE: Some functions will also transform each element individually

sqrt(x)

log(x)

# ==============================================================================

# USECASE: Other functions will summarize the vector with a single number

length(x)

sum(x)

mean(x)

Strings

  • When talking to R, we need a way to distinguish
    • Object/function names (e.g., the mean function)
    • Text/character data (e.g., the word mean)
  • Strings are R’s way of storing text data
    • Strings can store any characters (no rules!)
    • Strings are created and displayed with quotes
  • R has great tools for working with strings
    • Strings can be collected into vectors
    • Special functions can transform strings

name <- "John Doe"

Strings Live Coding

# USECASE: Strings are the main way to store character data in R
 
my_color <- red # error

my_color <- "red" # correct

# ==============================================================================

# USECASE: Strings can also store symbols not allowed in object names

dye <- "red#40"
dye

dyes <- c("red#40", "blue#02")
dyes

# ==============================================================================

# PITFALL: Many operations you can do to numbers won't work for strings

dyes + 1 # error

mean(dyes) # error

# ==============================================================================

# USECASE: But other operations work for both or even just for strings

length(dyes)

nchar(dyes)

dyes2 <- toupper(dyes)
dyes2

Packages

  • Cookbooks are a great way to learn to cook
    • They contain lots of recipes and instructions
    • Browse an online bookstore for a cookbook
    • Order it to add it to your personal bookshelf
    • To use, pull the cookbook off the shelf
  • Packages are like cookbooks for R
    • They contain helpful functions and datasets
    • Browse an online repository for a package
    • Install it to add it to your personal library
    • To use, load the package from the library

library("pkg_name")

Packages Live Coding

# USECASE: The stringr package adds a function to fix capitalization

students <- c("mary anne", "BENjamin", "Lee")

# ==============================================================================

# PITFALL: But we can't use that function without installing the package

str_to_title(students) # error

# ==============================================================================

# LESSON: Installing a package using RStudio

# - RStudio > Extras pane > Packages tab > Install button

# ==============================================================================

# PITFALL: We also need to load the package before we can use it

str_to_title(students) # error

# ==============================================================================

# LESSON: We load the package using library()

library("stringr")
str_to_title(students) #finally works!

# ==============================================================================

# LESSON: We can also keep our packages updated using RStudio

# RStudio > Extras pane > Packages tab > Update button

Importing and Exporting

  • Data is usually stored in data files
    • Importing files into R is called reading
    • Exporting files from R is called writing
  • A convenient data file type is a CSV
    • This stands for comma-separated values
    • A CSV file is easy to share with other people
  • The tidyverse package can read/write CSVs
    • Other packages can read/write other types (e.g., readxl, haven, rio, googlesheets4)

Read/Write Live Coding

# SETUP: Load the tidyverse package (if you haven't yet)

library(tidyverse)

# ==============================================================================

# USECASE: Read in a file containing data

my_data <- read_csv("jz2017.csv")
my_data

# NOTE: read_csv() will examine and guess the data type of each variable.
# You can tell it the data type of each variable, but that is more advanced.

# ==============================================================================

# USECASE: Write data back to a file

write_csv(my_data, file = "jz2017b.csv")

# NOTE: You can see the new file in Extras pane > Files tab.
# You can open the file in another program (e.g., Microsoft Excel).
# You can also email this file to someone else to share it.

{circumplex}

Package Website

https://circumplex.jmgirard.com

Package Overview

Instrument Functions

  • The package contains information about numerous circumplex instruments (i.e., questionnaires)
  • You can browse and learn about instruments
    • Who created it? What paper should I cite?
    • What are the response options and anchors?
    • What are the items’ numbers and text?
    • How do I score each scale from the items?
    • What normative data sets are available?
  • You can automatically score your item-level data
  • You can automatically norm your scale-level data

Instruments Live Coding

# SETUP: Load the circumplex package for use

library(circumplex)

# ==============================================================================

# USECASE: List all available instruments

instruments()

# ==============================================================================

# USECASE: Display general information about an instrument

print(csip) # brief

summary(csip) # detailed

# ==============================================================================

# USECASE: Display specific information about an instrument

items(ipipipc)

scales(ipipipc)

scales(ipipipc, items = TRUE)

anchors(ipipipc)

norms(ipipipc)

# ==============================================================================

# USECASE: Automatically score an instrument from item-level data

raw_iipsc

raw_scores <- score(raw_iipsc, items = IIP01:IIP32, instrument = iipsc)
raw_scores

# ==============================================================================

# USECASE: Automatically standardize an instrument from stored norms

norms(iipsc)

z_scores <- standardize(raw_scores, scales = PA:NO, angles = octants(),
                        instrument = iipsc, sample = 1)
z_scores

Basic SSM Analysis

  • The package performs basic SSM analyses
  • The Structural Summary Method (SSM)
    • Summarizes cicumplex (e.g., octant) scores
    • Reduces eight numbers down to just three
    • Each number has a distinct interpretation
    • Allows plotting in a circular space
  • Uncertainty and inference through resampling
    • e.g., bootstrapping or MCMC

Basic SSM Live Coding

jz2017

# ==============================================================================

# Calculate the overall sample's mean IIP-SC profile

overall_ssm <- ssm_analyze(
  .data = jz2017,
  scales = c(PA, BC, DE, FG, HI, JK, LM, NO),
  angles = c(90, 135, 180, 225, 270, 315, 360, 45),
)
summary(overall_ssm)

ssm_table(overall_ssm)

ssm_plot(overall_ssm)

# ==============================================================================

# Some shortcuts if your scales are already in order from PA to NO

overall_ssm <- ssm_analyze(
  .data = jz2017,
  scales = PA:NO,
  angles = octants()
)
summary(overall_ssm)

# ==============================================================================

# Project the NARPD measure into the IIP-SC circumplex space

narpd_ssm <- ssm_analyze(
  .data = jz2017,
  scales = PA:NO,
  angles = octants(),
  measures = NARPD
)

summary(narpd_ssm)

ssm_table(narpd_ssm)

ssm_plot(narpd_ssm)

Intermediate SSM Analysis

  • The package performs intermediate SSM analyses
  • Estimate SSM parameters for multiple groups and/or multiple measures simultaneously
    • Easier syntax for the analyst
    • Uses the same resamples
    • Populates the same tables/figures
  • Statistically contrast groups and/or measures
    • Compare each pair of groups/measures
    • Infer whether each parameter differs

Intermediate SSM Live Coding

jz2017

# ==============================================================================

# Calculate each gender group's mean IIP-SC profile

gender_ssm <- ssm_analyze(
  .data = jz2017,
  scales = PA:NO,
  angles = octants(),
  grouping = Gender
)
summary(gender_ssm)

ssm_table(gender_ssm)

ssm_plot(gender_ssm)

# ==============================================================================

# Statistically contrast the two gender groups' SSM parameters

gender_contrast <- ssm_analyze(
  .data = jz2017,
  scales = PA:NO,
  angles = octants(),
  grouping = Gender,
  contrast = "test"
)
summary(gender_contrast)

ssm_table(gender_contrast)

ssm_plot(gender_contrast)

# ==============================================================================

# Project the NARPD and ASPD measures into the IIP-SC circumplex space

pds_ssm <- ssm_analyze(
  .data = jz2017,
  scales = PA:NO,
  angles = octants(),
  measures = c(NARPD, ASPD)
)

summary(pds_ssm)

ssm_table(pds_ssm)

ssm_plot(pds_ssm)

# ==============================================================================

# Statistically contrast the NARPD and ASPD measures' SSM parameters

pds_contrast <- ssm_analyze(
  .data = jz2017,
  scales = PA:NO,
  angles = octants(),
  measures = c(NARPD, ASPD),
  contrast = "test"
)

summary(pds_contrast)

ssm_table(pds_contrast)

ssm_plot(pds_contrast)

Horizons

  • SSM extensions (from SITAR 2021)
  • Circumplex fit analyses
  • Circumplex reliability analyses
  • Functions for scoring EMA data
  • Functions for tidying joystick data
  • A rewritten, web-based DARMA